package top.itpath.common.util;

import cn.hutool.extra.spring.SpringUtil;
import com.auth0.jwt.JWT;
import com.auth0.jwt.JWTCreator;
import com.auth0.jwt.algorithms.Algorithm;
import com.auth0.jwt.interfaces.DecodedJWT;
import org.springframework.stereotype.Component;
import top.itpath.admin.entity.SysUser;
import top.itpath.config.ApplicationProperties;

import java.time.Duration;
import java.util.Date;

/**
 * @author zhaomengru
 * create by  2023/10/10 - 16:17
 * jwt工具
 */
@Component
public class JwtUtil {

    public static String createToken(SysUser user) {
        ApplicationProperties properties = SpringUtil.getBean(ApplicationProperties.class);
        return createToken(user, Duration.ofSeconds(properties.getTokenExpireTime()), properties.getDefaultSign());
    }

    public static String createToken(SysUser user, Duration duration) {
        ApplicationProperties properties = SpringUtil.getBean(ApplicationProperties.class);
        return createToken(user, duration, properties.getDefaultSign());
    }

    public static String createToken(SysUser user, Duration duration, String secret) {
        JWTCreator.Builder builder = JWT.create();
        builder.withClaim("username", user.getUsername())
                .withClaim("id", user.getId())
                .withExpiresAt(new Date(System.currentTimeMillis() + duration.toMillis()));
        return builder.sign(Algorithm.HMAC256(secret));
    }

    public static void verifyToken(String token) {
        ApplicationProperties properties = SpringUtil.getBean(ApplicationProperties.class);
        JWT.require(Algorithm.HMAC256(properties.getDefaultSign())).build().verify(token);
    }

    public static SysUser getSubject() {
        return parseToken(RequestUtil.getToken());
    }

    public static SysUser parseToken(String token) {
        ApplicationProperties properties = SpringUtil.getBean(ApplicationProperties.class);
        JWT jwt = new JWT();
        DecodedJWT decodedJWT = jwt.decodeJwt(token);
        SysUser sysUser = new SysUser();
        sysUser.setId(decodedJWT.getClaim("id").asLong());
        sysUser.setUsername(decodedJWT.getClaim("username").asString());
        return sysUser;
    }
}
